package config;

import java.io.BufferedWriter;
import java.io.File;
import java.io.FileWriter;
import java.io.IOException;
import java.util.Calendar;
import java.util.Date;

import javax.swing.JOptionPane;

import org.json.simple.JSONObject;

import view.admin.AdminFrame;
import data.HttpRequest;

/**
 * 
 * @author Yang Wang <yang@digitalmenubox.com>
 */
public class Debug {

	public static final boolean debugEnabled = true;
	public static final int MSG_LEVEL = 0;
	public static final int SYSTEM_LEVEL = 1;
	public static final int WARNING_LEVEL = 2;
	public static final int EXCEPTION_LEVEL = 3;
	public static final int ERROR_LEVEL = 4;

	public static final int LOG_STARTING_PLAYER = 10000; // the player has just
															// started
	public static final int LOG_RESTARTING_PLAYER = 10001; // the player is
															// shutting down and
															// will restart
															// shortly
	public static final int LOG_FILE_DOWNLOADED = 10001; // the player received
															// the resource
	public static final int LOG_RECEIVED_RESOURCE_FILE = 10001;
	public static final int LOG_FTP_FILE_NOT_EXIST = 10001;
	public static final int LOG_HTTP_FILE_NOT_EXIST = 10001;
	public static final int LOG_SQL_EXCEPTION = 10001;
	public static final int LOG_IO_EXCEPTION = 10001;
	public static final int LOG_DATABASE_NOT_ACCESSIBLE = 10001;

	public static final int LOG_INVALID_IMAGE_TYPE = 10;
	public static final int LOG_FTP_MISSING_FILE = 10;
	public static final int LOG_HTTP_MISSING_FILE = 10;

	public static void msg(String message) {
		if (debugEnabled) {
			System.out.println(message);
		}
	}

	public static void log(String message) {
		log(message, MSG_LEVEL);
	}

	public static void log(String message, int level) {
		// precondition: none
		// postcondition: a file named YYMMDD.txt is created if does not exist,
		// logs are written into the log file.
		if (!isAcceptableLogLevel(level)) {
			return;
		}
		Calendar today = Calendar.getInstance();
		String filename = String.format("%1$4d%2$02d%3$02d.txt", today.get(Calendar.YEAR), today.get(Calendar.MONTH) + 1, today.get(Calendar.DAY_OF_MONTH));

		// create a log file if it does not exist
		File logFile = new File(config.Settings.getLogsDirectory() + filename);
		if (!logFile.exists() && config.Settings.getLogsDirectory()!=null) {
			try {
				logFile.getParentFile().mkdirs();
				logFile.createNewFile();
			} catch (IOException ex) {
				System.err.println("Error creating log file : " + logFile.getAbsolutePath());
				return;
			}
		}

		// append the message to the log
		try {
			if(config.Settings.getLogsDirectory()!=null) appendMessageToLogFile(message, logFile);
		} catch (IOException ex) {
			System.err.println("Error appending to log file : " + logFile.getAbsolutePath());
			return;
		}

		// ignores any level below the message_level, the dashboard does not
		// have to see this.
		if (level > MSG_LEVEL) {
			sendLogMessageToServer(message, level);
		}

	}

	private static boolean appendMessageToLogFile(String message, File logFile) throws IOException {
		// precondition: message != null, logFile.exists() == true
		// postcondition: the String message is appened to the end of the log
		// file
		BufferedWriter br = null;
		try {
			br = new BufferedWriter(new FileWriter(logFile, true));
			Date date = new Date();
			br.write(date.toString() + " " + message);
			br.newLine();
			br.flush();
		} finally {
			br.close();
		}
		return true;
	}

	private static boolean isAcceptableLogLevel(int level) {
		// precondition: none
		// postcondition: returns true if the log level is defined in this class
		if (level >= Debug.MSG_LEVEL && level <= Debug.ERROR_LEVEL) {
			return true;
		}

		return false;
	}

	private static void sendLogMessageToServer(String message, int level) {
		// precondition: none;
		// postcondition: log information is sent to the server
		JSONObject obj = new JSONObject();
		obj.put("log_message", message);
		obj.put("level", level);
		HttpRequest.postLog(obj.toString());
	}

	public static void showDatabaseAccessErrorAlert(String error) {
		Settings.setDatabaseIsAccessible(false);
		Debug.log("Could not connect to local MySql database, please check the username and password.", Debug.ERROR_LEVEL);
		// Logger.getLogger(Settings.class.getName()).log(Level.SEVERE, null,
		// ex);
		// AdminFrame.getInstance().setVisible(true);
		// JOptionPane.showMessageDialog(AdminFrame.getInstance(), error);
	}
}
